package com.gitee.sop.layui.adminserver.frameword.init.config.plus;

import com.gitee.sop.layui.adminserver.frameword.init.bo.AdminRealm;
import com.gitee.sop.layui.adminserver.frameword.init.properties.ShiroProperties;
import com.gitee.sop.layui.adminserver.plugins.shiro.ModelRealmAuthenticator;
import com.gitee.sop.layui.adminserver.plugins.shiro.PermissionAuthenticationFilter;
import com.gitee.sop.layui.adminserver.plugins.shiro.ShiroMobileSessionManager;
import org.apache.shiro.authc.pam.AtLeastOneSuccessfulStrategy;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.realm.Realm;
import org.apache.shiro.spring.LifecycleBeanPostProcessor;
import org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.context.WebApplicationContext;

import javax.servlet.Filter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author: huwei
 * @date: 2019/9/18 14:56
 * @version: 1.0.0
 */
@Configuration
public class ShiroPlusConfig {

    @Bean(name = "shiroFilter")
    public ShiroFilterFactoryBean shiroFilter(SecurityManager manager, ShiroProperties properties, PermissionAuthenticationFilter permissionAuthenticationFilter) {
        //shiro配置
        ShiroFilterFactoryBean bean = new ShiroFilterFactoryBean();
        bean.setSecurityManager(manager);

        Map<String, Filter> filters = new HashMap<>(1);
        filters.put("perm", permissionAuthenticationFilter);
        //自定义filter设置
        bean.setFilters(filters);

        //配置登录的url和登录成功的url
        bean.setLoginUrl(properties.getLoginUrl());
        bean.setSuccessUrl(properties.getSuccessUrl());

        //配置url拦截
        bean.setFilterChainDefinitionMap(properties.urlFilter());
        return bean;
    }

    /**
     * 自定义shiro权限拦截器，用于总控系统功能
     *
     * @return
     */
    @Bean(name = "permissionAuthenticationFilter")
    public PermissionAuthenticationFilter permissionAuthenticationFilter(WebApplicationContext webApplicationContext) {
        return new PermissionAuthenticationFilter(webApplicationContext);
    }

    @Bean(name = "securityManager")
    public SecurityManager securityManager(ModelRealmAuthenticator modelRealmAuthenticator
            , AdminRealm adminRealm) {
        DefaultWebSecurityManager manager = new DefaultWebSecurityManager();
        manager.setAuthenticator(modelRealmAuthenticator);
        //配置realm
        List<Realm> realmList = new ArrayList<>(2);
        realmList.add(adminRealm);
        manager.setRealms(realmList);

        //移动
        manager.setSessionManager(new ShiroMobileSessionManager());

        return manager;
    }

    @Bean
    public ModelRealmAuthenticator modelRealmAuthenticator() {
        ModelRealmAuthenticator modelRealmAuthenticator = new ModelRealmAuthenticator();
        modelRealmAuthenticator.setAuthenticationStrategy(new AtLeastOneSuccessfulStrategy());
        return modelRealmAuthenticator;
    }

    @Bean
    public LifecycleBeanPostProcessor lifecycleBeanPostProcessor() {
        return new LifecycleBeanPostProcessor();
    }

    @Bean
    public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator() {
        DefaultAdvisorAutoProxyCreator creator = new DefaultAdvisorAutoProxyCreator();
        creator.setProxyTargetClass(true);
        return creator;
    }

    @Bean
    public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor(@Qualifier("securityManager") SecurityManager manager) {
        AuthorizationAttributeSourceAdvisor advisor = new AuthorizationAttributeSourceAdvisor();
        advisor.setSecurityManager(manager);
        return advisor;
    }
}
